1 /** 2 Copyright: Copyright (c) 2018, Joakim Brännström. All rights reserved. 3 License: $(LINK2 http://www.boost.org/LICENSE_1_0.txt, Boost Software License 1.0) 4 Author: Joakim Brännström (joakim.brannstrom@gmx.com) 5 */ 6 module code_checker.engine.types; 7 8 @safe: 9 10 public import code_checker.cli : ConfigStaticCode, ConfigClangTidy, Compiler, 11 Logging; 12 13 /** The base fixture that an analyzer implement 14 */ 15 interface BaseFixture { 16 /// Explain what the analyser is. 17 string explain(); 18 19 /// The environment the analysers execute in. 20 void putEnv(Environment); 21 22 /// Setup the environment for analyze. 23 void setup(); 24 25 /// Execute the analyser. 26 void execute(); 27 28 /// Cleanup after analyze. 29 void tearDown(); 30 31 /// Returns: the result of the analyzer. 32 Result result(); 33 } 34 35 /// Environment data useful for an anylser. 36 struct Environment { 37 import code_checker.types : AbsolutePath; 38 import code_checker.compile_db : CompileCommandDB, CompileCommandFilter; 39 40 ConfigStaticCode staticCode; 41 ConfigClangTidy clangTidy; 42 Compiler compiler; 43 Logging logg; 44 45 /// Flags the user wants to be automatically removed from the compile_commands.json. 46 CompileCommandFilter flagFilter; 47 48 /// Command to generate the compile_commands.json 49 string genCompileDb; 50 51 /// The compile_commands.json that contains all files to analyse. 52 AbsolutePath compileDbFile; 53 54 /// The compile commands that is used for the analyse. 55 CompileCommandDB compileDb; 56 57 /// The files to analyse 58 string[] files; 59 } 60 61 /// The summary of an analyzers result. 62 enum Status { 63 none, 64 /// The analyze failed 65 failed, 66 /// The analyze passed without any remarks. 67 passed 68 } 69 70 Status mergeStatus(Status old, Status new_) @safe pure nothrow @nogc { 71 if (old == Status.none) 72 return new_; 73 return old == Status.failed ? old : new_; 74 } 75 76 /// The amount of points the analyzer adjusts the overall score 77 struct Score { 78 int value; 79 alias value this; 80 } 81 82 /// The severity of a user message. 83 enum MsgSeverity { 84 /// Why an analyzer failed to execute 85 unableToExecute, 86 /// Why an analyzer reports failed 87 failReason, 88 /// Improvement suggestions for how to fix the score intended for the user 89 improveSuggestion, 90 } 91 92 /// A message from an analyzer. 93 struct Msg { 94 MsgSeverity severity; 95 string value; 96 alias value this; 97 98 int opCmp(ref const Msg rhs) @safe pure nothrow const { 99 if (severity < rhs.severity) 100 return -1; 101 else if (severity > rhs.severity) 102 return 1; 103 else 104 return value < rhs.value ? -1 : (value > rhs.value ? 1 : 0); 105 } 106 107 bool opEquals(ref const Msg o) @safe pure nothrow const @nogc scope { 108 return severity == o.severity && value == o.value; 109 } 110 111 string toString() @safe const { 112 import std.format : format; 113 114 return format("%s: %s", severity, value); 115 } 116 } 117 118 /// Messages from an analyzer intended to be displayed to the user. 119 struct Messages { 120 Msg[] value; 121 alias value this; 122 } 123 124 /// Suggestions of how to improve the score. 125 struct Suggestions { 126 Msg[] value; 127 alias value this; 128 } 129 130 /// The result of an analyzer. 131 struct Result { 132 /// The summary state of an analyzer after it has executed. 133 Status status; 134 Score score; 135 /// Messages from the analyzer to the user. 136 Messages msg; 137 } 138 139 /// The result of all analyzers. 140 struct TotalResult { 141 /// Total status of all analyzers 142 Status status; 143 144 /// Total score of the analyzers 145 Score score; 146 147 /// Improvement suggestions for the user 148 Suggestions sugg; 149 } 150 151 /// Classification of warnings. Used by the user to filter on. 152 /// This enum must be ordered such that style < low < medium < high < critical 153 enum Severity { 154 style, 155 low, 156 medium, 157 high, 158 critical 159 } 160 161 /// Returns: a nullable severity translation from a string. 162 auto toSeverity(string s) @safe pure nothrow { 163 import std.typecons : Nullable; 164 import std.conv : to; 165 166 Nullable!Severity r; 167 168 try { 169 r = s.to!Severity; 170 } catch (Exception e) { 171 } 172 173 return r; 174 }